package es.us.idinfor.rmplugin.example;

import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Set;

import Jama.Matrix;

import com.google.common.collect.Lists;
import com.rapidminer.example.Attribute;
import com.rapidminer.example.ExampleSet;
import com.rapidminer.operator.OperatorException;
import com.rapidminer.tools.att.AttributeSet;

import es.us.idinfor.rmplugin.algorithm.GMatrix;

/**
 * This class is responsible of creating examples.
 * 
 * @author Miguel Angel Alvarez de la Concepcion
 */
public class ExamplesFactory {
	
	/**
	 * This method creates a subset of a example without some features.
	 * This features are indicated by a matrix.
	 * 
	 * @param original The original example set.
	 * @param m The matrix of features.
	 * @return A copy of the original example set.
	 */
	public static ExampleSet getCopy(ExampleSet original, Matrix m) throws OperatorException {
		ExampleSet res = getCopy(original);
		Set<Attribute> attributes = GMatrix.getAttributeSubset(original, m);
		Iterator<Attribute> it = res.getAttributes().allAttributes();
		Attribute label = res.getAttributes().getLabel();
		Attribute att = null;
		
		while(it.hasNext()) {
			att = it.next();
			
			if(!attributes.contains(att) && !att.equals(label)) {
				it.remove();
			}
		}
		
		att = null;
		label = null;
		it = null;
		attributes = null;
		
		return res;
	}
	
	/**
	 * This method creates a copy of an example set.
	 * 
	 * @param original The original example set.
	 * @return A copy of the original example set.
	 */
	public static ExampleSet getCopy(ExampleSet original) throws OperatorException {
		OptimizedMemoryExampleTable table = OptimizedMemoryExampleTable.createCompleteCopy(original.getExampleTable());
		List<Attribute> attributes = Lists.newArrayList(table.getAttributes());
		AttributeSet set = new AttributeSet(attributes, new HashMap<String, Attribute>());
		Attribute label = table.findAttribute(original.getAttributes().getLabel().getName());
		ExampleSet res = table.createExampleSet(set);
		res.getAttributes().setLabel(label);
		
		label = null;
		set = null;
		attributes = null;
		table = null;
		
		return res;
	}

	/**
	 * This method creates a subset of an example set.
	 * 
	 * @param es The original example set.
	 * @param label The name of the label attribute.
	 * @param cad The label that the examples have.
	 * @return A subset of the original example set.
	 * @throws OperatorException It is thrown when the subset can not be returned.
	 */
	public static ExampleSet getSubSet(ExampleSet es, String labelName, String cad) throws OperatorException {
		double cadValue = es.getAttributes().getLabel().getMapping().getIndex(cad);
		OptimizedMemoryExampleTable table = null;
		List<Attribute> attributes = null;
		AttributeSet set = null;
		Attribute label = null;
		ExampleSet res = null;
		
		if(cadValue != -1) {
			table = OptimizedMemoryExampleTable.createSubCopy(es.getExampleTable(), labelName, cadValue);
			attributes = Lists.newArrayList(table.getAttributes());
			set = new AttributeSet(attributes, new HashMap<String, Attribute>());
			label = table.findAttribute(labelName);
			res = table.createExampleSet(set);
			res.getAttributes().setLabel(label);
			
			label = null;
			set = null;
			attributes = null;
			table = null;
		}
		
		return res;
	}
}
